#pragma once
using namespace Ogre;

class CHD_SDK_API Camera
{
public:
	Camera(void);
public:
	~Camera(void);
	Vector3 getDirection(){
		return rot * Vector3(0,0,-1);
	}
	void setRotation(Real pitch,Real yaw,Real roll)
	{
		this->yaw = yaw;
		this->roll = roll;
		this->pitch = pitch;


		Quaternion rot1;
		rot1.FromAngleAxis(Radian(Math::DegreesToRadians(pitch)),Vector3(1,0,0));
		Quaternion rot2;
		rot2.FromAngleAxis(Radian(Math::DegreesToRadians(yaw)),Vector3(0,1,0));
		Quaternion rot3;
		rot3.FromAngleAxis(Radian(Math::DegreesToRadians(roll)),Vector3(0,0,-1));
		rot = rot3*rot2*rot1;
	}
	void moveX(Real value){
		setPosition(getPosition()+rot.xAxis()*value);
	}
	void moveY(Real value){
		setPosition(getPosition()+rot.yAxis()*value);
	}
	void moveZ(Real value){
		setPosition(getPosition()+rot.zAxis()*value);
	}

	Real getRoll(){
		return roll;
	}
	Real getYaw(){
		return yaw;
	}
	Real getPitch(){
		return pitch;
	}
	Quaternion getRotation(){
		return rot;
	}
	void setPosition(const Vector3& pos){
		this->pos = pos;
	}
	Vector3 getPosition(){
		return pos;
	}
	void setFovy(double fovy){
		this->fovy = fovy;
	}
	double getFovy(){
		return fovy;
	}
	void setAspect(double aspect){
		this->aspect = aspect;
	}
	double getAspect(){
		return aspect;
	}
	void setNear(double zNear){
		this->zNear = zNear;
	}
	double getNear(){
		return zNear;
	}
	void setFar(double zFar){
		this->zFar = zFar;
	}
	double getFar(){
		return zFar;
	}
	void update(int matrixMode = GL_MODELVIEW);
private:
	Vector3 pos;
	Quaternion rot;
	Real yaw;
	Real roll;
	Real pitch;

	double fovy;
	double aspect;
	double zNear;
	double zFar;
};
